package com.gxatek.cockpit.dvr.service;

import android.Manifest;
import android.app.ProgressDialog;
import android.content.Context;
import android.content.DialogInterface;
import android.content.pm.PackageManager;
import android.graphics.Color;
import android.hardware.Sensor;
import android.hardware.SensorEvent;
import android.hardware.SensorEventListener;
import android.hardware.SensorManager;
import android.os.Build;
import android.os.Bundle;
import android.os.Handler;
import android.os.HandlerThread;
import android.os.Looper;
import android.os.Message;
import android.text.TextUtils;
import android.util.Log;
import android.view.LayoutInflater;
import android.view.View;
import android.widget.AdapterView;
import android.widget.ArrayAdapter;
import android.widget.Button;
import android.widget.CheckBox;
import android.widget.CompoundButton;
import android.widget.EditText;
import android.widget.LinearLayout;
import android.widget.Spinner;
import android.widget.TextView;
import android.widget.Toast;

import androidx.annotation.NonNull;
import androidx.annotation.RequiresApi;
import androidx.appcompat.app.AlertDialog;
import androidx.appcompat.app.AppCompatActivity;

import com.gxatek.cockpit.dvr.service.view.CustomLineChart;
import com.gxatek.cockpit.dvr.service.R;

import java.io.BufferedWriter;
import java.io.File;
import java.io.FileWriter;
import java.io.IOException;
import java.io.RandomAccessFile;
import java.nio.ByteBuffer;
import java.nio.channels.FileChannel;
import java.text.SimpleDateFormat;
import java.time.format.DateTimeFormatter;
import java.util.ArrayList;
import java.util.Collections;
import java.util.Comparator;
import java.util.Date;
import java.util.List;
import java.util.Locale;

/**
 * 用MPAndroidChart显示加速度的数据，数据是之前在androidStudio里输出的，copy到了文件里，然后读取文件，显示x,y,z的值
 * 说明：
 * 已经将采集apk的包名，从com.senseauto.sensordemo改成了com.gxatek.cockpit.dvr.service，在T68上，改了名称后，才能采集到5ms的sensor数据（没改包名，10ms的sensor采集不到）
 * 这个包名和星河集成的哨兵的包名一样，需要采集的时候先暂时移除哨兵的apk（/system/app/SYDvrService，整个目录pull到本地，然后删除这个包下的内容，再将我们的采集apk push到这个目录下）
 * 采集完后，在把采集apk删了，把刚pull出来的哨兵的apk再复原push回去
 */
public class DemoActivity extends AppCompatActivity implements SensorEventListener {
    private SensorManager sensorManager;
    private Sensor accelerometer;
    String TAG = "DemoActivity";

    List<Item> list = new ArrayList<>();
    //拍打时间内的数据
    List<Item> childDataList = new ArrayList<>();
    //点击时间的时间集合，用来生成文件名用到
    List<String> timeList = new ArrayList<>();
    //权限是否有了
    boolean isAllGranted = false;

    //是否开始采集sensor数据
    boolean isRecordStart = false;

    boolean actionHasStart = false;

    int MAX_COUNT = 3000;//5分钟的内容大概3000条，超过了就得删除之前的数据了，预防oom

    SimpleDateFormat childThreadSdf = new SimpleDateFormat("yyyy-MM-dd_HH_mm_ss_SSS");
    SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd_HH_mm_ss_SSS");
    SimpleDateFormat fileNameSdf = new SimpleDateFormat("MM-dd_HH_mm_ss_SSS");
    private static final ThreadLocal<SimpleDateFormat> threadLocalSdf = new ThreadLocal<SimpleDateFormat>() {
        @Override
        protected SimpleDateFormat initialValue() {
            return new SimpleDateFormat("yyyy-MM-dd_HH_mm_ss_SSS", Locale.getDefault());
        }
    };
    Button btnRecord, btnAction;

    //某一次，所有的采集获取的数据写入的文件
    File dataFile;

    HandlerThread mHandlerThread;
    //单次拍打的数据，写入的文件
    /*RandomAccessFile file;
    FileChannel channel;*/
    private BufferedWriter writer;
    Handler mChildHandler;
    //拍打结束的弹框view
    View dialogView;
    //拍打结束，写入文件的等待框
    ProgressDialog progressDialog;
    Spinner spinner;
    int selectedPosition = 0;
    int MSG_DIALOG_SHOW = 101;
    int MSG_DIALOG_HIDE = 102;
    int MSG_DATA_SAVE_SUCCESS = 100;
    int MSG_DATA_SAVE_FAIL = 99;
    int MSG_WRITE_ARRAY1 = 1;
    int MSG_WRITE_ARRAY2 = 2;

    int MAX_LINE_SHOW_COUNT = 500;//整个能显示下多少个点的数据
    List<Float> xDataList = new ArrayList<>();
    List<Float> yDataList = new ArrayList<>();
    List<Float> zDataList = new ArrayList<>();
    CustomLineChart markerView, yMarkView, zMarkView;
    TextView tvResult;
    LinearLayout linePanel;
    boolean isShowLinePanel = false;
    boolean hasSetMaxMin = false;
    CheckBox checkBox;
    public static int MAX_ARRAY_COUNT = 20;
    //一个用来存数据，存到10条，数据就放大另一个集合里，然后把这个存满数据的集合handler发子线程里去写入文件中，减少写文件的频繁度
    ArrayList<Item>array1 = new ArrayList<>(MAX_ARRAY_COUNT);
    ArrayList<Item>array2 = new ArrayList<>(MAX_ARRAY_COUNT);
    boolean flagWriteArray1 = true;

    int SENSOR_DELAY_TYPE[] = {SensorManager.SENSOR_DELAY_NORMAL, //对应android底层的枚举值 3
            SensorManager.SENSOR_DELAY_UI,
            SensorManager.SENSOR_DELAY_GAME,
            SensorManager.SENSOR_DELAY_FASTEST,
            5000,
            10000
            };

    Handler handler = new Handler(Looper.getMainLooper()) {
        @Override
        public void handleMessage(@NonNull Message msg) {
            super.handleMessage(msg);
            if (msg.what == MSG_DIALOG_SHOW) {
                if (progressDialog == null) {
                    progressDialog = new ProgressDialog(DemoActivity.this);
                    progressDialog.setMessage("文件写入中，请等待...");
                    progressDialog.setCancelable(false);
                }
                progressDialog.show();
            } else if (msg.what == MSG_DIALOG_HIDE) {
                if (progressDialog != null) {
                    progressDialog.dismiss();
                }
            } else if (msg.what == MSG_DATA_SAVE_SUCCESS) {
                Log.e(TAG, "消息，data文件写入成功了 ");
                Toast.makeText(DemoActivity.this, "拍打数据写入完成", Toast.LENGTH_SHORT).show();
                childDataList.clear();
                actionHasStart = false;
                timeList.clear();
            } else if (msg.what == MSG_DATA_SAVE_FAIL) {
                Log.e(TAG, "消息，data文件写入失败");
                childDataList.clear();
                timeList.clear();
                actionHasStart = false;
            }

        }
    };

    /**
     * 原本加了折线图的效果的，后面觉得折线图是额外的需求，可以先不显示
     * @param savedInstanceState
     */
    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_demo);
        if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.S) {//安卓12及以后的版本, 需要有HIGH_SAMPLING_RATE_SENSORS的权限才能采集高频率的sensor数据,这个权限还得加系统应用配置sharedUserId配置和系统签名
            if (checkCallingPermission(Manifest.permission.BODY_SENSORS) != PackageManager.PERMISSION_GRANTED
                    && checkCallingPermission(Manifest.permission.WRITE_EXTERNAL_STORAGE) != PackageManager.PERMISSION_GRANTED
                    && checkCallingPermission(Manifest.permission.HIGH_SAMPLING_RATE_SENSORS) != PackageManager.PERMISSION_GRANTED
                    && checkCallingPermission(Manifest.permission.READ_EXTERNAL_STORAGE) != PackageManager.PERMISSION_GRANTED) {
                requestPermissions(new String[]{Manifest.permission.BODY_SENSORS, Manifest.permission.WRITE_EXTERNAL_STORAGE, Manifest.permission.READ_EXTERNAL_STORAGE}, 10);
            }
        } else if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M) {//6.0系统
            if (checkCallingPermission(Manifest.permission.BODY_SENSORS) != PackageManager.PERMISSION_GRANTED
                    && checkCallingPermission(Manifest.permission.WRITE_EXTERNAL_STORAGE) != PackageManager.PERMISSION_GRANTED
                    && checkCallingPermission(Manifest.permission.READ_EXTERNAL_STORAGE) != PackageManager.PERMISSION_GRANTED) {
                requestPermissions(new String[]{Manifest.permission.BODY_SENSORS, Manifest.permission.WRITE_EXTERNAL_STORAGE, Manifest.permission.READ_EXTERNAL_STORAGE}, 10);
            } else {
                afterPermissionGranted();
            }
        } else {
            afterPermissionGranted();
        }
        tvResult = findViewById(R.id.tvClickResult);
        linePanel = findViewById(R.id.linePanel);
        checkBox = findViewById(R.id.checkbox);
        isShowLinePanel = checkBox.isChecked();
        checkBox.setOnCheckedChangeListener(new CompoundButton.OnCheckedChangeListener() {
            @Override
            public void onCheckedChanged(CompoundButton buttonView, boolean isChecked) {
                isShowLinePanel = isChecked;
                linePanel.setVisibility(isShowLinePanel ? View.VISIBLE : View.GONE);
            }
        });
        findViewById(R.id.bt_back).setOnClickListener(v->{
            if(isRecordStart){
                isRecordStart = false;
                stopRecordAccelerometer();
            }
            finish();
        });
        linePanel.setVisibility(isShowLinePanel ? View.VISIBLE : View.GONE);

        markerView = findViewById(R.id.xMarkerView);
        markerView.setLineColor(Color.BLACK);
        markerView.setPointColor(Color.RED);
        markerView.setPointSize(1);
        markerView.setDesc("x轴");
        markerView.setDescPaintColor(R.color.teal_200);
        markerView.setOnPointClickListener(new CustomLineChart.PointClickListener() {
            @Override
            public void onClick(int index) {
                Item item = list.get(index);
                if (item != null) {
                    float x = item.values[0];
                    tvResult.setText("x: " + x + "\t时间：" + sdf.format(item.date));
                }
            }
        });

        yMarkView = findViewById(R.id.yMarkerView);
        yMarkView.setLineColor(Color.BLACK);
        yMarkView.setPointColor(Color.RED);
        yMarkView.setDesc("y轴");
        yMarkView.setPointSize(1);
        yMarkView.setDescPaintColor(R.color.purple_500);

        yMarkView.setOnPointClickListener(new CustomLineChart.PointClickListener() {
            @Override
            public void onClick(int index) {
                Item item = list.get(index);
                if (item != null) {
                    float x = item.values[1];
                    tvResult.setText("y: " + x + "\t时间：" + sdf.format(item.date));
                }
            }
        });

        zMarkView = findViewById(R.id.zMarkerView);
        zMarkView.setLineColor(Color.BLACK);
        zMarkView.setPointColor(Color.RED);
        zMarkView.setPointSize(1);
        zMarkView.setDesc("z轴");
        zMarkView.setDescPaintColor(R.color.teal_700);

        zMarkView.setOnPointClickListener(new CustomLineChart.PointClickListener() {
            @Override
            public void onClick(int index) {
                Item item = list.get(index);
                if (item != null) {
                    float x = item.values[2];
                    tvResult.setText("z: " + x + "\t时间：" + sdf.format(item.date));
                }
            }
        });

        findViewById(R.id.btnResetClick).setOnClickListener(v -> {
            resetClickLine();
        });

        btnRecord = findViewById(R.id.btnStart);
        btnRecord.setOnClickListener(v -> {
            resetClickLine();
            if (!isRecordStart) {//未开始
                Log.e(TAG, "开始采集sensor数据了");
                isRecordStart = true;
                btnRecord.setText(getResources().getString(R.string.sensor_record_stop));
                btnRecord.setTextColor(getResources().getColor(R.color.red));
                startRecordAccelerometer();
                Toast.makeText(this, "数据采集开始！", Toast.LENGTH_SHORT).show();
            } else {
                Log.e(TAG, "结束采集sensor数据了");
                isRecordStart = false;
                btnRecord.setText(getResources().getString(R.string.sensor_record_start));
                btnRecord.setTextColor(getResources().getColor(R.color.white));
                stopRecordAccelerometer();
                Toast.makeText(this, "数据采集结束！", Toast.LENGTH_SHORT).show();
            }
        });

        btnAction = findViewById(R.id.btnActionStart);
        btnAction.setOnClickListener(v -> {
            resetClickLine();
            if (!actionHasStart) { //第一次点击，认为是开始拍打记录时间
                actionHasStart = true;
                timeList.add("start_" + fileNameSdf.format(new Date()));//记录一个开始时间
                btnAction.setText(getString(R.string.sensor_action_stop));//文字描述改成拍打结束
                btnAction.setTextColor(getResources().getColor(R.color.red));
            } else {
                timeList.add("_end_" + fileNameSdf.format(new Date()));
                //弹框让用户输入名称，输入完成之后，将 childDataList 里的内容写入另一个文件，这个文件名 和timeList有关系，还有弹框输出的内容描述
                actionHasStart = false;
                btnAction.setText(getString(R.string.sensor_action_start));
                btnAction.setTextColor(getResources().getColor(R.color.white));

                LayoutInflater inflater = this.getLayoutInflater();
                dialogView = inflater.inflate(R.layout.dialog_layout, null);
                AlertDialog dialog = new AlertDialog.Builder(this)
                        .setCancelable(false)
                        .setView(dialogView).setPositiveButton("确定", new DialogInterface.OnClickListener() {
                            @Override
                            public void onClick(DialogInterface dialog, int which) {
                                EditText editTextId = dialogView.findViewById(R.id.editTextId);
                                EditText editTextDesc = dialogView.findViewById(R.id.editTextDesc);
                                String idStr = editTextId.getText().toString().trim();
                                if (TextUtils.isEmpty(idStr)) {
                                    idStr = "";
                                }
                                String desc = editTextDesc.getText().toString().trim();
                                if (TextUtils.isEmpty(desc)) {
                                    desc = "";
                                }
                                Log.e(TAG, "idStr=" + idStr + " desc=" + desc + " timeList.size=" + timeList.size() + " 期间记录数量dataList.size:" + childDataList.size());
                                dialog.dismiss();
                                dataWriteFile(idStr, desc);
                            }
                        })
                        .create();
                dialog.show();
            }
        });

        spinner = findViewById(R.id.spinner);
        List<String> data = new ArrayList<>();


        data.add("DELAY_NORMAL(100ms)");
        data.add("DELAY_UI(50ms)");
        data.add("DELAY_GAME(20ms)");
        data.add("DELAY_FAST(5ms)");
        data.add("5000(5ms)");
        data.add("DELAY_100HZ(10ms)");

        ArrayAdapter<String> adapter = new ArrayAdapter<String>(
                this,
                R.layout.spinner_item,
                R.id.tv,
                data);
        spinner.setAdapter(adapter);
        spinner.setSelection(0);
        selectedPosition = 0;
        spinner.setOnItemSelectedListener(new AdapterView.OnItemSelectedListener() {
            @Override
            public void onItemSelected(AdapterView<?> parentView, View selectedItemView, int position, long id) {
                if(selectedPosition!= position){
                    if(isRecordStart){ //已经开始录制了
                        spinner.setSelection(selectedPosition);
                        Log.e(TAG, "thread:"+Thread.currentThread().getName());
                        Toast.makeText(DemoActivity.this, "请先停止sensor采集再更换数据频率", Toast.LENGTH_SHORT).show();
                    }
                }
            }

            @Override
            public void onNothingSelected(AdapterView<?> parent) {

            }
        });
    }

    public void resetClickLine() {
        markerView.resetClickLine();
        yMarkView.resetClickLine();
        zMarkView.resetClickLine();
    }

    //某一次拍打时，获取到的这个时间段内的信息数据，参数是描述信息
    private void dataWriteFile(String id, String desc) {
        Message msg = handler.obtainMessage(MSG_DIALOG_SHOW);
        msg.sendToTarget();
        new Thread() {
            @Override
            public void run() {
                super.run();
                StringBuffer nameBuffer = new StringBuffer("action_");
                if (!TextUtils.isEmpty(id)) {
                    nameBuffer.append(id).append("_");
                }
                if (!TextUtils.isEmpty(desc)) {
                    nameBuffer.append(desc).append("_");
                }
                for (int i = 0; i < timeList.size(); i++) {
                    nameBuffer.append(timeList.get(i));
                }
                nameBuffer.append(".txt");
                File targetFile = new File(getSaveDir(), nameBuffer.toString());
                Log.e(TAG, "targetFile=" + targetFile.getAbsolutePath());
                try {

                    if (!targetFile.exists()) {
                        targetFile.createNewFile();
                    }
                    //用来解决偶现的数据有一两条插入在集合中，文件里的内容有一两头混乱的数据插入在正常的排序数据里问题
                    // 使用 Comparator 按 date 升序排序
                    //时间错误大概率是系统时间联网后更新了，导致后面的数据获取的system.currentTime值小了，这里不做重新排序的操，就按放到集合的数据来写入
                    /*Collections.sort(childDataList, new Comparator<Item>() {
                        @Override
                        public int compare(Item item1, Item item2) {
                            return item1.date.compareTo(item2.date);
                        }
                    });*/
                    //这里的子线程，也单独用自己的sdf,不要和主线程的sdf共用，免得格式化出来的时间不对
                    SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd_HH_mm_ss_SSS");
                    BufferedWriter writer = new BufferedWriter(new FileWriter(targetFile));
                    for (int i = 0; i < childDataList.size(); i++) {
                        StringBuffer buffer = new StringBuffer();
                        Item item = childDataList.get(i);
                        buffer.append("time=").append(sdf.format(item.date));
                        buffer.append("\tx=").append(item.values[0]).append("\ty=").append(item.values[1]).append("\tz=").append( item.values[2]).append("\n");
                        String data = buffer.toString();
                        // 假设你的集合是String类型
                        writer.write(data);
                    }
                    writer.close();
                    handler.sendEmptyMessage(MSG_DIALOG_HIDE);
                    handler.sendEmptyMessage(MSG_DATA_SAVE_SUCCESS);
                } catch (IOException e) {
                    e.printStackTrace();
                    handler.sendEmptyMessage(MSG_DIALOG_HIDE);
                    handler.sendEmptyMessage(MSG_DATA_SAVE_FAIL);
                }
            }
        }.start();
    }

    private void startRecordAccelerometer() {
        /**
         * 车机上最快好像也就是100ms
         * SENSOR_DELAY_FASTEST 最低延迟 0us，一般不推荐使用，该种模式可能造成手机电力大量消耗，会影响手机性能
         * SENSOR_DELAY_GAME 游戏延迟 20,000 us，一般绝大多数的实时性较高的游戏都使用该级别
         * SENSOR_DELAY_UI 界面延迟 60,000 us ，一般对于屏幕方向自动旋转使用，相对节省电能和逻辑处理，一般游戏开发中我们不使用。
         * SENSOR_DELAY_NORMAL 标准延迟 200,000 us，200ms ，对于一般的简单小游戏可以使用，但过低的采样率可能对一些赛车类游戏有跳帧现象。
         */
        int position = spinner.getSelectedItemPosition();
        Log.e(TAG, "position=" + position+" type:"+SENSOR_DELAY_TYPE[position]);
        sensorManager.registerListener(this, accelerometer, SENSOR_DELAY_TYPE[position]);
        //开始写文件操作了，存dataList里的内容
        startThreadWriteFile();
    }
    @RequiresApi(api = Build.VERSION_CODES.N)
    @Override
    public void onSensorChanged(SensorEvent event) {
        float x = event.values[0];
        float y = event.values[1];
        float z = event.values[2];
        long time = System.currentTimeMillis();
        Log.e(TAG, "onSensorChanged x="+x+" y="+y+" z="+z+" time="+time+" timestamp="+event.timestamp+" 格式化time:"+sdf.format(new Date(time)));

        if (isRecordStart) {
            //这里需要发消息给子线程，写入到文件里
            Item item = new Item(new float[]{x, y, z}, new Date(time), time);
            if(flagWriteArray1){
                if(array1.size()<MAX_ARRAY_COUNT){
                    array1.add(item);
                }
                if(array1.size() == MAX_ARRAY_COUNT){//array1的数据满了，将array1的数据保存下来，接下来的数据都要先写入到array2里去
                    Message msg = mChildHandler.obtainMessage();
                    msg.what = MSG_WRITE_ARRAY1;
                    mChildHandler.sendMessage(msg);
                    flagWriteArray1 = false;
                }
            }else{
                if(array2.size()<MAX_ARRAY_COUNT){
                    array2.add(item);
                }
                if(array2.size()==MAX_ARRAY_COUNT){ //array2的数据满了，将array2的数据保存下来，接下来的数据都要先写入到array1里去
                    Message msg = mChildHandler.obtainMessage();
                    msg.what = MSG_WRITE_ARRAY2;
                    mChildHandler.sendMessage(msg);
                    flagWriteArray1 = true;
                }
            }
            /*Message msg = mChildHandler.obtainMessage();
            msg.obj = item;
            mChildHandler.sendMessage(msg);*/
            if(!hasSetMaxMin){
                hasSetMaxMin = true;
                markerView.setMaxValue(x);
                markerView.setMinValue(x);

                yMarkView.setMaxValue(y);
                yMarkView.setMinValue(y);

                zMarkView.setMaxValue(z);
                zMarkView.setMinValue(z);
            }

            //临时存到动作数组里，最好不要存放太多，免得oom
            if (timeList.size() > 0 && actionHasStart) { //点击过开始拍打
                if (childDataList.size() >= MAX_COUNT) {
                    childDataList.remove(0);
                }
                childDataList.add(new Item(new float[]{x, y, z}, new Date(time), time));
            }
            if (isShowLinePanel) { //勾选了展示，view才会显示出来
                //界面能显示的最多数量，超过了最大显示数量，移除旧的数据
                if (list.size() >= MAX_LINE_SHOW_COUNT) { //这个用来做点击时的处理，展示对应点击的那个点附近的数据信息
                    list.remove(0);
                }
                list.add(new Item(new float[]{x, y, z}, new Date(time), time));

                if (xDataList.size() >= MAX_LINE_SHOW_COUNT) {
                    xDataList.remove(0);
                }
                xDataList.add(x);
                markerView.setData(xDataList);
                markerView.invalidate();

                if (yDataList.size() >= MAX_LINE_SHOW_COUNT) {
                    yDataList.remove(0);
                }
                yDataList.add(y);
                yMarkView.setData(yDataList);
                yMarkView.invalidate();


                if (zDataList.size() >= MAX_LINE_SHOW_COUNT) {
                    zDataList.remove(0);
                }
                zDataList.add(z);
                zMarkView.setData(zDataList);
                zMarkView.invalidate();
            }
        }
    }
    private void startThreadWriteFile() {
        mHandlerThread = new HandlerThread("mHandlerThread");
        mHandlerThread.start();
        dataFile = new File(getSaveDir(), "all_" + fileNameSdf.format(new Date()) + ".txt");
        Log.e(TAG, "dataFile=" + dataFile.getAbsolutePath());
        try {
            if (!dataFile.exists()) {
                dataFile.createNewFile();
            }
            writer = new BufferedWriter(new FileWriter(dataFile));
            /*file = new RandomAccessFile(dataFile.getAbsolutePath(), "rw");
            channel = file.getChannel();*/
        } catch (Exception e) {
            e.printStackTrace();
        }
        //发消息，通过channel写入文件里
        mChildHandler = new Handler(mHandlerThread.getLooper()) {
            @Override
            public void handleMessage(Message msg) {
                //对信息的相关处理操作
                //在子线程mHandlerThread中运行
                super.handleMessage(msg);
                if(msg.what == MSG_WRITE_ARRAY2){
                    //Log.e(TAG, "收到2的消息，写入array2的数据到文件");
                    writeArrayData(array2);
                    array2.clear();
                    //Log.e(TAG, "array2 wirte一次数据结束");
                }else if(msg.what == MSG_WRITE_ARRAY1){ //对array1的数据写入文件里
                    //Log.e(TAG, "收到1的消息，写入array1的数据到文件");
                    writeArrayData(array1);
                    array1.clear();
                    //Log.e(TAG, "array1 wirte一次数据结束");
                }
                /*Item item = (Item) msg.obj;
                if (item != null && item.values != null) {
                    Log.e(TAG, "handleMessage收到的数据写入文件：x="+item.values[0]+"  y="+item.values[1]+" z="+item.values[2]
                            +" time:"+item.time+" time format后："+sdf.format(item.date));
                    StringBuffer bufferData = new StringBuffer();
                    bufferData.append("time=").append(sdf.format(item.date));
                    bufferData.append("\tx=").append( item.values[0]).append("\ty=").append( item.values[1]).append("\tz=").append(  item.values[2]).append("\n");
                    String data = bufferData.toString();
                    // 打印要写入的数据
                    Log.e(TAG, "准备写入的数据: " + data+"   数据长度是："+data.length());
                    try {
                        writer.write(data);
                    } catch (IOException e) {
                        e.printStackTrace();
                    }
                    Log.e(TAG, "wirte一次数据结束！写入数据对应的时间点：item.time="+item.time);
                }*/
            }
        };

    }

    //将换成的array里的数据写到文件里，一下写多条
    private void writeArrayData(ArrayList<Item>list){
        StringBuffer bufferData = new StringBuffer();
        //子线程每次写入20条数据，都用的一个sdf来格式化时间，效率不是很高，但是研究那边说保持格式和之前的相同
        SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd_HH_mm_ss_SSS");
        for(int i=0;i<list.size();i++){
            StringBuffer buffer = new StringBuffer();
            Item item = list.get(i);
            String dateStr = sdf.format(item.date);
            //Log.e(TAG, MAX_ARRAY_COUNT+"条数据到文件：x="+item.values[0]+"  y="+item.values[1]+" z="+item.values[2] +" time:"+item.time+" time format后："+dateStr);
            buffer.append("time=").append(dateStr);
            buffer.append("\tx=").append( item.values[0]).append("\ty=").append( item.values[1]).append("\tz=").append(  item.values[2]).append("\n");
            //Log.e(TAG, "某一条格式后的数据: " + buffer.toString());
            bufferData.append(buffer);
        }
        String data = bufferData.toString();
        //Log.e(TAG, "一下写入"+MAX_ARRAY_COUNT+"条数据的长度:"+data.length());
        try {
            writer.write(data);
        } catch (IOException e) {
            e.printStackTrace();
        }
    }
    private void stopRecordAccelerometer() {
        sensorManager.unregisterListener(this);
        //停止流写文件
        isRecordStart = false;
        stopWriteFileThread();
        String name = dataFile.getName();
        String array[] = name.split(".txt");
        File finalFile = new File(getSaveDir(), array[0] + "_to_" + fileNameSdf.format(new Date()) + ".txt");
        boolean flag = dataFile.renameTo(finalFile);
        if (flag) { //复制成功，原始文件删除
            dataFile.delete();
        }
        Log.e(TAG, "stopRecordAccelerometer 重命名文件：" + flag + " finalFile=" + finalFile.getAbsolutePath());
    }

    private void stopWriteFileThread() {
        Log.e(TAG, "stopWriteFileThread()");
        try {
            /*if (channel != null) {
                channel.close();
                channel = null;
            }
            if (file != null) {
                file.close();
                file = null;
            }*/
            Log.e(TAG, "结束采集线程，先将缓存的数据先给写完");
            if(array1.size()>0){
                Log.e(TAG, "结束采集线程,array1还有数据");
                writeArrayData(array1);
            }
            if(array2.size()>0){
                Log.e(TAG, "结束采集线程,array2还有数据");
                writeArrayData(array2);
            }
            if(writer!=null){
                writer.close();
                writer = null;
            }
        } catch (Exception e) {
            e.printStackTrace();
        }
    }

    private void afterPermissionGranted() {
        sensorManager = (SensorManager) getSystemService(Context.SENSOR_SERVICE);
        accelerometer = sensorManager.getDefaultSensor(Sensor.TYPE_ACCELEROMETER);
    }

    @Override
    public void onRequestPermissionsResult(int requestCode, @NonNull String[] permissions, @NonNull int[] grantResults) {
        super.onRequestPermissionsResult(requestCode, permissions, grantResults);
        Log.e(TAG, "onRequestPermissionsResult->permissions.length=" + permissions.length + " granted.length=" + grantResults.length);
        isAllGranted = true;
        for (int i = 0; i < grantResults.length; i++) {
            if (grantResults[i] != PackageManager.PERMISSION_GRANTED) {
                isAllGranted = false;
                break;
            }
        }
        if (isAllGranted) {
            afterPermissionGranted();
        }
    }

    @Override
    protected void onResume() {
        super.onResume();
        Log.e(TAG, "onResume");
        if (isAllGranted) {
            //Log.e(TAG, "onResume startRecordAccelerometer");
            //startRecordAccelerometer();
        }
    }

    @Override
    protected void onPause() {
        super.onPause();
        Log.e(TAG, "onPause");
        if (isRecordStart) {
            Log.e(TAG, "onPause stopRecordAccelerometer");
            stopRecordAccelerometer();
        }
    }



    @Override
    public void onAccuracyChanged(Sensor sensor, int accuracy) {
        Log.e(TAG, "onAccuracyChanged");
    }

    @Override
    protected void onDestroy() {
        super.onDestroy();
        Log.e(TAG, "onDestroy");
        if (isRecordStart) {
            stopRecordAccelerometer();
        }
    }
    public String getSaveDir(){
        //车机用内置sd卡存放数据，平板用外置sd卡存放数据
        //return getExternalCacheDir().getAbsolutePath();
        String dirStr = getCacheDir().getAbsolutePath();
        File dir = new File(dirStr);
        if(!dir.exists()){
            dir.mkdirs();
        }
        return dirStr;
    }
}